package com.teacher.game.framework.util;

import java.util.Queue;
import java.util.concurrent.ConcurrentLinkedQueue;

/**
 * 通用对象池 - 减少垃圾回收压力，提升性能
 * 支持任何类型对象的重用管理
 * 
 * @param <T> 池中对象类型
 */
public abstract class ObjectPool<T> {
    
    // 使用线程安全的队列
    private final Queue<T> pool = new ConcurrentLinkedQueue<>();
    private final int maxPoolSize;
    private int currentSize = 0;
    private int totalCreated = 0; // 记录总创建数量
    
    /**
     * 创建对象池
     * @param maxPoolSize 最大池容量
     */
    public ObjectPool(int maxPoolSize) {
        this.maxPoolSize = maxPoolSize;
    }
    
    /**
     * 从池中获取对象（如果池为空则创建新对象）
     * @return 可用对象
     */
    public final T acquire() {
        T object = pool.poll();
        if (object == null) {
            object = createObject();
            totalCreated++;
        } else {
            currentSize--;
        }
        return object;
    }
    
    /**
     * 将对象归还到池中
     * @param object 要归还的对象
     */
    public final void release(T object) {
        if (object != null && currentSize < maxPoolSize) {
            resetObject(object);
            pool.offer(object);
            currentSize++;
        }
    }
    
    /**
     * 预填充对象池
     * @param count 预创建对象数量
     */
    public final void preFill(int count) {
        for (int i = 0; i < Math.min(count, maxPoolSize); i++) {
            T object = createObject();
            totalCreated++;
            resetObject(object);
            pool.offer(object);
            currentSize++;
        }
    }
    
    /**
     * 清空对象池
     */
    public final void clear() {
        pool.clear();
        currentSize = 0;
    }
    
    /**
     * 获取池中当前对象数量
     * @return 当前池中对象数量
     */
    public final int getPoolSize() {
        return currentSize;
    }
    
    /**
     * 获取最大池容量
     * @return 最大池容量
     */
    public final int getMaxPoolSize() {
        return maxPoolSize;
    }
    
    /**
     * 获取最大池容量（别名，与getMaxPoolSize相同）
     * @return 最大池容量
     */
    public final int getMaxSize() {
        return maxPoolSize;
    }
    
    /**
     * 获取当前活跃对象数量（估算值）
     * @return 活跃对象数量
     */
    public int getActiveCount() {
        return Math.max(0, totalCreated - currentSize);
    }
    
    /**
     * 获取总创建对象数量
     * @return 总对象数量
     */
    public int getTotalCount() {
        return totalCreated;
    }
    
    /**
     * 从池中移除一个对象（用于优化）
     * @return 移除的对象，如果池为空返回null
     */
    protected final T poll() {
        T object = pool.poll();
        if (object != null) {
            currentSize--;
        }
        return object;
    }
    
    /**
     * 创建新对象（子类必须实现）
     * @return 新创建的对象
     */
    protected abstract T createObject();
    
    /**
     * 重置对象状态（子类必须实现）
     * 在对象归还池中前调用，用于清理对象状态
     * @param object 要重置的对象
     */
    protected abstract void resetObject(T object);
}